package com.cqw.threaddemo.synchronize;

/**
 * $ javap -c -verbose SyncMethod.class
 *
 *
 * Classfile /F:/learning/ThreadDemo/target/classes/com/cqw/threaddemo/synchronize/SyncMethod.class
 *   Last modified 2021-1-15; size 425 bytes
 *   MD5 checksum 9d2eb28a231426f4ccef931593740831
 *   Compiled from "SyncMethod.java"
 * public class com.cqw.threaddemo.synchronize.SyncMethod
 *   minor version: 0
 *   major version: 52
 *   flags: ACC_PUBLIC, ACC_SUPER
 * Constant pool:
 *    #1 = Methodref          #4.#17         // java/lang/Object."<init>":()V
 *    #2 = Fieldref           #3.#18         // com/cqw/threaddemo/synchronize/SyncMethod.i:I
 *    #3 = Class              #19            // com/cqw/threaddemo/synchronize/SyncMethod
 *    #4 = Class              #20            // java/lang/Object
 *    #5 = Utf8               i
 *    #6 = Utf8               I
 *    #7 = Utf8               <init>
 *    #8 = Utf8               ()V
 *    #9 = Utf8               Code
 *   #10 = Utf8               LineNumberTable
 *   #11 = Utf8               LocalVariableTable
 *   #12 = Utf8               this
 *   #13 = Utf8               Lcom/cqw/threaddemo/synchronize/SyncMethod;
 *   #14 = Utf8               syncTask
 *   #15 = Utf8               SourceFile
 *   #16 = Utf8               SyncMethod.java
 *   #17 = NameAndType        #7:#8          // "<init>":()V
 *   #18 = NameAndType        #5:#6          // i:I
 *   #19 = Utf8               com/cqw/threaddemo/synchronize/SyncMethod
 *   #20 = Utf8               java/lang/Object
 * {
 *   public int i;
 *     descriptor: I
 *     flags: ACC_PUBLIC
 *
 *   public com.cqw.threaddemo.synchronize.SyncMethod();
 *     descriptor: ()V
 *     flags: ACC_PUBLIC
 *     Code:
 *       stack=1, locals=1, args_size=1
 *          0: aload_0
 *          1: invokespecial #1                  // Method java/lang/Object."<init>":()V
 *          4: return
 *       LineNumberTable:
 *         line 3: 0
 *       LocalVariableTable:
 *         Start  Length  Slot  Name   Signature
 *             0       5     0  this   Lcom/cqw/threaddemo/synchronize/SyncMethod;
 *
 *   public synchronized void syncTask();
 *     descriptor: ()V
 *     //方法标识ACC_PUBLIC代表public修饰，ACC_SYNCHRONIZED指明该方法为同步方法
 *     flags: ACC_PUBLIC, ACC_SYNCHRONIZED
 *     Code:
 *       stack=3, locals=1, args_size=1
 *          0: aload_0
 *          1: dup
 *          2: getfield      #2                  // Field i:I
 *          5: iconst_1
 *          6: iadd
 *          7: putfield      #2                  // Field i:I
 *         10: return
 *       LineNumberTable:
 *         line 8: 0
 *         line 9: 10
 *       LocalVariableTable:
 *         Start  Length  Slot  Name   Signature
 *             0      11     0  this   Lcom/cqw/threaddemo/synchronize/SyncMethod;
 * }
 * SourceFile: "SyncMethod.java"
 */
public class SyncMethod {

    public int i;

    /**
     * 方法级的同步是隐式的，字节码中并没有monitorenter指令和monitorexit指令，使用ACC_SYNCHRONIZED标识来指明该方法是一个同步方法
     * JVM通过该ACC_SYNCHRONIZED访问标志来辨别一个方法是否声明为同步方法，从而执行相应的同步调用。
     */
    public synchronized void syncTask(){
        i++;
    }
}